package com.qf.listener;

import com.qf.config.RabbitMQConfig;
import com.qf.constant.RabbitConstant;
import com.rabbitmq.client.Channel;
import org.springframework.amqp.core.ExchangeTypes;
import org.springframework.amqp.core.Message;
import org.springframework.amqp.rabbit.annotation.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.io.IOException;
import java.util.List;
import java.util.Map;

/**
 * 自定义监听器
 * @author lixu
 */
@Component
public class MyListener {


    /**
     * 监听queue1
     */
    @RabbitListener(queues = "queue1")
    public void receiverQueue1(String name){
        System.out.println("1号MyListener接收到的消息:" + name);
    }
    /**
     * 监听queue2
     */
    @RabbitListener(queues = "queue2")
    public void receiverQueue2(String name){
        System.out.println("2号MyListener接收到的消息:" + name);

    }
    /**
     * 监听queue2
     */
   // @RabbitListener(queues = "queue1")
/*    public void receiverQueue2(Map map){
        System.out.println("2号MyListener接收到的消息:" + map);

    }*/


    /**
     * 监听Q1
     */
    @RabbitListener(queues = "Q1")
    public void receiverQ1(String name){
        System.out.println("Q1MyListener接收到的消息:" + name);
    }
    /**
     * 监听Q2
     */
    @RabbitListener(queues = "Q2")
    public void receiverQ2(String name){
        System.out.println("Q2MyListener接收到的消息:" + name);
    }


    /**
     *      *   本次测试的
     *      *   注解创建交换机、队列、绑定
     */
    @RabbitListener(bindings = {@QueueBinding(
            value = @Queue(name = RabbitConstant.QUEUE_1_ANNO,durable = "true",autoDelete = "false"),
            exchange = @Exchange(value = RabbitConstant.EXCHANGE_TOPIC_ANNO,type = ExchangeTypes.TOPIC),
            key = {RabbitConstant.ROUTINGKEY1_ANNO}
    )})
    public void receiverQueue1Anno(String msg){
        System.out.println("Queue1Anno：接收消息:" + msg);
    }

    /**
     *      *   本次测试的
     *      *   注解创建交换机、队列、绑定
     */
    @RabbitListener(bindings = {@QueueBinding(
            value = @Queue(name = RabbitConstant.QUEUE_2_ANNO,durable = "true",autoDelete = "false"),
            exchange = @Exchange(value = RabbitConstant.EXCHANGE_TOPIC_ANNO,type = ExchangeTypes.TOPIC),
            key = {RabbitConstant.ROUTINGKEY2_ANNO,RabbitConstant.ROUTINGKEY3_ANNO}
    )})
    public void receiverQueue2Anno(String msg){
        System.out.println("Queue2Anno：接收消息:" + msg);
    }

    /**
     *      *   本次测试的
     *      *   Java配置类 创建交换机、队列、绑定
     *      接收消息第一种写法  queues = {RabbitMQConfig.QUEUE_1})
     */
    @RabbitListener(queues = {RabbitMQConfig.QUEUE_1})
    public void receiverJavaConfigurationQueue1(String msg){
        System.out.println("JavaConfigurationQueue1：接收消息:" + msg);
    }

    //@Autowired
    //private org.springframework.amqp.core.Queue queue2;
    /**
     *      *   本次测试的
     *      *   Java配置类 创建交换机、队列、绑定
     *     接收消息第二种写法  queues = {"#{queue2.name}"})
     */
    @RabbitListener(queues = {"#{queue2.name}"})
    public void receiverJavaConfigurationQueue2(String msg){
        System.out.println("JavaConfigurationQueue2：接收消息:" + msg);
        //JavaConfigurationQueue2：接收消息:本次222测试的Java配置类创建交换机、队列、绑定
    }


    /**
     * 测试消费者手动应答
     *    交换机
     *     1、fanout 扇出交换机   发布、订阅   routingkey 没有 ”“
     *     2、direct 定向交换机   路由     routingkey  c
     *     3、topic  主题        主题     routingkey  c.#   c.*
     *
     */
    @RabbitListener(bindings = {@QueueBinding(
            value = @Queue(name = "queue_c1",durable = "true",autoDelete = "false"),
            exchange = @Exchange(value = "exchange_c"),
            key = {"c",RabbitConstant.ROUTINGKEY3_ANNO}
    )})
    public void receiverC1(String msg, Channel channel, Message message){

        try {
            //1：接收消息  receiverC1(String msg){
            //2:打印  8行
            System.out.println("receiverC1：接收消息:" + msg);
            //3:抛出异常
            int i = 1/0;
            //4：.....
            //5:手动应答
            //long deliveryTag, 手动应答哪个消息 消息的标识 （ID）
            // boolean multiple ：手动应答 是否批量应答
            channel.basicAck(message.getMessageProperties().getDeliveryTag(),false);
        } catch (Exception e) {
            //判断当前消息是已经投递过了
            if(message.getMessageProperties().isRedelivered()){
                System.out.println("第二次是发过来的消息了");
                //是投递过的  第二次是发过来的消息了
                //拒绝接收消息了
                //long deliveryTag, 手动应答哪个消息 消息的标识 （ID）
                //boolean requeue : 是否将当前消息放回队列 （是否队列再投递一次） true:让队列再投递一次 、false:不再投递了
                try {
                    //打印日志
                    //人工介入
                    // 是否将当前消息放回队列  false:删除
                    channel.basicReject(message.getMessageProperties().getDeliveryTag(),false);

                } catch (IOException ex) {
                    //人工介入
                    //打印日志
                }
            }else{
                System.out.println("第一次发过来的消息");
                try {
                    //不执行手动确认机制
                    //long deliveryTag, 手动应答哪个消息 消息的标识 （ID）
                    // boolean multiple ：手动应答 是否批量应答
                    //boolean requeue : 是否将当前消息放回队列 （是否队列再投递一次） true:让队列再投递一次 、false:不再投递了
                    channel.basicNack(message.getMessageProperties().getDeliveryTag(),false,true);
                } catch (IOException ex) {
                    //throw new RuntimeException(ex);
                }
            }
        }
    }







}
